#!/usr/bin/env node
const { spawn } = require('child_process');
const { OpenAI } = require('openai')
const { default: inquirer } = require('inquirer');
const path = require('path');
const fs = require('fs');

async function main() {
    const chalk = (await import('chalk')).default;

        const config = {
        // apiKey: process.env.XXX_API_KEY,
        // baseURL: process.env.XXX_BASE_URL,
        // modal: process.env.XXX_MODEL,
        // apiKey: 'sk-ade9753627f04d7c8ae3b41ee5670ab1',
        // baseURL: 'https://dashscope.aliyuncs.com/compatible-mode/v1',
        // modal: 'qwen-plus',
        apiKey: '572fd2fd-0cc0-443c-a278-6e5271d942ed',
        baseURL: 'https://ark.cn-beijing.volces.com/api/v3',
        modal: 'deepseek-v3-1-terminus',
    }


    const client = new OpenAI({
        apiKey: config.apiKey,
        baseURL: config.baseURL,
    });

    const content =
        `生成 macOS shell 脚本

用户输入内容："${process.argv.slice(2).join(' ')}"

# 输出格式

## 脚本格式
返回示例: "ls"
格式说明: 此内容将直接被执行，仅包含单行脚本内容，不要包含无法执行的描述信息，也不要返回无用的\`\`\`等代码块。

# 规则
- 首要关注用户输入内容，严格按照输出格式返回
- 最终返回【脚本格式】，此格式务必返回纯脚本内容
- 对于section提示信息，能用就用，无用忽略就行


<section title="当前目录">
${process.cwd()} 
</section>

<section title="当前目录文件，最多10个">
${fs.readdirSync(process.cwd()).slice(0, 10).join('\n')}
</section>

<section title="用户设定">
收藏链接:
需求列表 https://ezone.ezone-i.work/project/ezOne/plan/tree
首页 https://ezone.ezone-i.work/home/jianglikui

记忆指令:
生成日报 'daily-report generate'
打开日报 'code /Users/mac/Desktop/文档空间/日报'
创建文件 'echo "文件内容" >> 文件名'
</section>
`
    function writeLog(content, filename = 'logForAiShell.txt') {
        try {
            const logPath = path.join(__dirname, filename);
            const dir = path.dirname(logPath);

            // 确保目录存在
            if (!fs.existsSync(dir)) {
                fs.mkdirSync(dir, { recursive: true });
            }

            // 写入内容（会自动创建文件）
            fs.writeFileSync(logPath, content + '\n\n', { flag: 'w' });

            console.log(`日志已写入: ${logPath}`);
        } catch (error) {
            console.error('写入日志失败:', error);
        }
    }
    writeLog(content)

    const messages = [{ role: "system", content }]

    const send = async () => {
        const completion = await client.chat.completions.create({
            messages: messages,
            model: config.modal,
            stream: true,
        });

        process.stdout.write('\n');
        let rs = ''
        // 逐字输出到终端
        for await (const part of completion) {
            const curr = part.choices[0].delta.content
            rs += curr
            if (rs.startsWith('question')) {
                // 清空当前行
                process.stdout.clearLine();
                process.stdout.cursorTo(0);
                continue;
            }
            process.stdout.write(chalk.green(curr));
        }
        process.stdout.write('\n\n');

        if (rs.startsWith('question')) {
            messages.push({ role: "assistant", content: rs })
            const qs = rs.split('\n').filter((item) => !item.startsWith('question'))
            const answer = await inquirer.prompt([
                {
                    type: 'list',
                    name: 'answer',
                    message: '请选择:',
                    choices: qs.map((item, index) => ({ name: item, value: index }))
                }
            ]);
            messages.push({ role: "user", content: qs[answer.answer] })
            await send();
            return;
        }

        inquirer.prompt([
            {
                type: 'list',
                name: 'action',
                message: '请选择操作:',
                choices: [
                    { name: '执行', value: 'run' },
                    { name: '追加提示信息', value: 'generate' },
                    { name: '退出 [ctrl+c]', value: 'exit' }
                ],
                default: 'run'
            }
        ]).then(async (answers) => {
            switch (answers.action) {
                case 'run':
                    console.log(chalk.yellow('\n正在执行命令:\n'));
                    try {
                        const child = spawn(rs, {
                            shell: true,
                            stdio: 'inherit'
                        });

                        child.on('close', (code) => {
                            if (code !== 0) {
                                console.error(chalk.red(`\n命令执行失败，退出码: ${code}`));
                            } else {
                                console.log(chalk.green('\n命令执行完成。'));
                            }
                        });

                        child.on('error', (err) => {
                            console.error(chalk.red(`\n执行命令时出错: ${err}`));
                        });

                    } catch (error) {
                        console.error(chalk.red('执行命令失败:', error));
                    }
                    break;
                case 'generate':
                    messages.push({ role: "assistant", content: rs })
                    // 先让用户输入提示信息
                    const userInput = await inquirer.prompt([
                        {
                            type: 'input',
                            name: 'tip',
                            message: '请输入提示信息:',
                        }
                    ]);
                    // 提示信息用用户角色追加到 messages
                    messages.push({ role: "user", content: userInput.tip });
                    await send();
                    break;
                case 'exit':
                    console.log('退出...');
                    break;
            }
        }).catch((e) => {
            console.log(e);
        });
    }
    await send();
}

main()